package com.alibaba.citrus.cr.unified.inventory.facade.service;

import com.alibaba.citrus.cr.common.annotation.FacadeInvoker;
import com.alibaba.citrus.cr.common.util.TimeUtil;
import com.alibaba.cz.base.tool.log.Log;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.lattice2.epoch.sdk.model.Result;
import com.epoch.app.bcorder.model.dto.BaselineQueryScItemByPageFromDbRequest;
import com.epoch.app.bcorder.model.dto.EmployeeGetCurrentLoginResponse;
import com.epoch.app.bcorder.model.dto.GetLoginEmployeeInfoResponse;
import com.epoch.app.bcorder.model.dto.OrganizationSDO;
import com.epoch.app.bcorder.model.dto.SearchCargoZoneListByDBRequest;
import com.epoch.app.bcorder.model.dto.SearchCargoZoneListByDBResponse;
import com.epoch.app.bcorder.model.dto.WarehouseInfo;
import com.epoch.app.bcorder.service.BaseDataService;
import com.epoch.app.bcorder.service.BcOrderService;
import com.epoch.app.bcorder.service.UnifiedInventoryService;
import com.epoch.app.crplatformenhance.model.dto.GetDownOrganizationListRequest;
import com.epoch.app.crplatformenhance.model.dto.GetTopOrganizationListRequest;
import com.epoch.app.crplatformenhance.model.dto.ScItemSDO;
import com.epoch.app.crplatformenhance.model.dto.TopOrganizationListResponse;
import com.epoch.app.crplatformenhance.service.CrPlatformEnhanceService;
import com.epoch.app.crunifiedinventory.inventoryread.dto.MixQueryInventoryRequest;
import com.epoch.app.crunifiedinventory.inventoryread.dto.MixQueryInventoryResponse;
import com.epoch.app.crunifiedinventory.inventoryread.dto.SumInventoryQuantityRequest;
import com.epoch.app.crunifiedinventory.inventoryread.service.InventoryReadService;
import com.epoch.app.crunifiedinventory.model.dto.AllocateUnshippedQuantitySDO;
import com.epoch.app.crunifiedinventory.model.dto.BatchGetAllocateUnShippedQuantityRequest;
import com.epoch.app.crunifiedinventory.model.dto.BusinessInventoryDTO;
import com.epoch.app.crunifiedinventory.model.dto.GetListWarehouseStockByPageRequest;
import com.epoch.app.crunifiedinventory.model.dto.InventoryStatistic;
import com.epoch.app.crunifiedinventory.model.dto.InventoryStatisticData;
import com.epoch.app.crunifiedinventory.model.dto.InventorySumQuantityResponse;
import com.epoch.app.crunifiedinventory.model.dto.QueryListWarehouseStockForPageRequest;
import com.epoch.app.crunifiedinventory.model.dto.SumTotalQuantityRequest;
import com.epoch.app.crunifiedinventory.service.CrUnifiedInventoryService;
import com.google.common.collect.Lists;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.context.annotation.Primary;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.Future;
import java.util.stream.Collectors;

/**
 * @description: 库存合计查询
 * @author: yuhw
 * @date: 2023年01月03日 20:02
 **/
@Service
@Primary
public class InventoryReadServiceImpl implements InventoryReadService {

    private Log log = Log.getLogger(InventoryReadServiceImpl.class);
    
    @Resource
    private CrUnifiedInventoryService crUnifiedInventoryService;
    @Resource
    private UnifiedInventoryService unifiedInventoryService;
    @Resource
    private BaseDataService baseDataService;
    @Resource
    private CrPlatformEnhanceService crPlatformEnhanceService;
    @Resource
    private BcOrderService bcOrderService;
    @Resource(name="logsCheckSyncTaskExecutor")
    private ThreadPoolTaskExecutor taskExecutor;
    //共享仓
    private static final Integer SHARE_WAREHOUSE_TYPE = 2;
    //公司层级类型
    private static final Integer COMPANY_TYPE = 103;
    private static final Integer SALE_ORG_TYPE = 104;
    private static final Integer SALES_CHANNEL_TYPE = 105;
    private static final Integer SALES_DEPARTMENT_TYPE = 106;
    private static final Integer BATCH_INVENTORY = 2;
    private static final Integer CAR_INVENTORY = 3;
    private static final Integer MAX_PAGE_SIZE = 1000;

    /**
     * 库存数量合计
     * @param sumInventoryQuantityRequest
     * @return
     */
    @Override
    @FacadeInvoker
    public Result<InventorySumQuantityResponse> sumInventoryQuantity(SumInventoryQuantityRequest sumInventoryQuantityRequest) {
        //仓库的获取问题 当选择了仓库档案或者 逻辑仓库 工厂编码 库存地点时,  获取预占的仓库入参 和 统计库存的仓库入参是有区别的
        //货品的获取 兼容货品编码框是
        String goodsId = sumInventoryQuantityRequest.getGoodsId();
        List<String> goodsIds = Lists.newArrayList();
        if (StringUtils.isNotBlank(sumInventoryQuantityRequest.getGoodsCode())){
            //页面输入货品编码后  取货品编码和货品id的交集
            goodsIds = getMixedGoodsIds(sumInventoryQuantityRequest);
            if (CollectionUtils.isEmpty(goodsIds)){
                return Result.success(null);
            }
        }else if (StringUtils.isNotBlank(goodsId)){
            //如果只传了货品id 只设置货品id
            goodsIds.add(goodsId);
        }
        log.info("sumInventoryQuantity_godsId:{}",goodsId);
        log.info("sumInventoryQuantity_godsIds:{}",JSON.toJSONString(goodsIds));
        SearchCargoZoneListByDBRequest searchCargoZoneListRequest = new SearchCargoZoneListByDBRequest();
        if (StringUtils.isAnyBlank(sumInventoryQuantityRequest.getRelatedOrganizationId(),
                sumInventoryQuantityRequest.getRelatedOrganizationType())){
            log.info("sumInventoryQuantity_orgError:{}",JSON.toJSONString(sumInventoryQuantityRequest));
            return Result.success(null);
        }

//        如果选了逻辑仓库类型 则销售组织必填
//        if (sumInventoryQuantityRequest.getStoreType() != null && StringUtils.isBlank(sumInventoryQuantityRequest.getSaleOrgId())){
//            log.error("sumInventoryQuantity_saleOrgError:{}",JSON.toJSONString(sumInventoryQuantityRequest));
//            return Result.success(null);
//        }
        //登录人的组织层级
        String orgId = sumInventoryQuantityRequest.getRelatedOrganizationId();
        Integer type = Integer.parseInt(sumInventoryQuantityRequest.getRelatedOrganizationType());
        //限制权限
        boolean limitPermission = true;
        if ( type == 105 || type == 106){
            String saleOrgId = getSaleOrgId(orgId);
            if (StringUtils.isBlank(saleOrgId)){
                log.error("sumInventoryQuantity_saleOrgIdError");
                return Result.success(null);
            }
            //如果销售组织和当前的不匹配
            if (StringUtils.isNotBlank(sumInventoryQuantityRequest.getSaleOrgId()) && !sumInventoryQuantityRequest.getSaleOrgId().equals(saleOrgId)){
                return Result.success(null);
            }
            searchCargoZoneListRequest.setSaleOrgIdList(Lists.newArrayList(saleOrgId));
        }else if (type == 104){
            if (StringUtils.isNotBlank(sumInventoryQuantityRequest.getSaleOrgId()) && !sumInventoryQuantityRequest.getSaleOrgId().equals(orgId)){
                return Result.success(null);
            }
            searchCargoZoneListRequest.setSaleOrgIdList(Lists.newArrayList(orgId));
        }else if (type == 103){
            List<String> downSaleOrgIds = getDownSaleOrgIds(orgId);
            if (CollectionUtils.isEmpty(downSaleOrgIds)){
                log.error("sumInventoryQuantity_downSaleOrgIds_error");
                return Result.success(null);
            }
            if (StringUtils.isNotBlank(sumInventoryQuantityRequest.getSaleOrgId()) && !downSaleOrgIds.contains(sumInventoryQuantityRequest.getSaleOrgId())){
                return Result.success(null);
            }
            searchCargoZoneListRequest.setSaleOrgIdList(downSaleOrgIds);
        }else if (type > 106){
            log.error("sumInventoryQuantity_noPermission");
            return Result.success(null);
        }else {
            limitPermission = false;
            //高权限账号选择了销售组织需要限制销售组织
            if (StringUtils.isNotBlank(sumInventoryQuantityRequest.getSaleOrgId())){
                searchCargoZoneListRequest.setSaleOrgIdList(Lists.newArrayList(sumInventoryQuantityRequest.getSaleOrgId()));
            }
        }
        //判断是否有涉及仓库的入参
        boolean hasWarehouseParams = StringUtils.isNotBlank(sumInventoryQuantityRequest.getFactoryCode()) ||
                StringUtils.isNotBlank(sumInventoryQuantityRequest.getWarehouseCode()) ||
                CollectionUtils.isNotEmpty(sumInventoryQuantityRequest.getWarehouseIdList())
                || CollectionUtils.isNotEmpty(sumInventoryQuantityRequest.getWarehouseAreaIdList())
                || StringUtils.isNotBlank(sumInventoryQuantityRequest.getSaleOrgId());
//                || sumInventoryQuantityRequest.getStoreType() != null;

        //仓库档案 仓库id 工厂编码 库存地点 + 销售组织 + 逻辑仓库类型
        List<WarehouseInfo> warehouseAreaList;
        List<String> warehouseAreaIdList = null;
        List<String> shareWarehouseAreaIdList;
        //如果有仓库请求参数
        //这里限制类型
        if (sumInventoryQuantityRequest.getStoreType() != null){
            searchCargoZoneListRequest.setTypeList(Lists.newArrayList(sumInventoryQuantityRequest.getStoreType()));
        }
        if (hasWarehouseParams){
            warehouseAreaList = getWarehouseAreaList(sumInventoryQuantityRequest,searchCargoZoneListRequest);
            if (CollectionUtils.isEmpty(warehouseAreaList)){
                return Result.success(null);
            }
            warehouseAreaIdList = warehouseAreaList.stream().map(WarehouseInfo::getId).filter(StringUtils::isNotBlank)
                .collect(Collectors.toList());
        }else {
            if (limitPermission){
                warehouseAreaList = getWarehouseAreaList(sumInventoryQuantityRequest,searchCargoZoneListRequest);
                if (CollectionUtils.isEmpty(warehouseAreaList)){
                    return Result.success(null);
                }
                //权限有限制时需要限制住只获取当前权限下的逻辑仓库
                warehouseAreaIdList = warehouseAreaList.stream().map(WarehouseInfo::getId).collect(Collectors.toList());
            }else {
                //当是高权限时, 直接去获取共享仓
                searchCargoZoneListRequest.setTypeList(Lists.newArrayList(SHARE_WAREHOUSE_TYPE));
                warehouseAreaList = getWarehouseAreaList(sumInventoryQuantityRequest,searchCargoZoneListRequest);
            }
        }
        shareWarehouseAreaIdList = getShareWarehouseAreaIdList(warehouseAreaList);
        log.info("sumInventoryQuantity_getUnShippedQuantity:{}",JSON.toJSONString(shareWarehouseAreaIdList));
        //获取调拨单的未发数量 虚拟预占
        Long unShippedQuantity = getUnShippedQuantity(shareWarehouseAreaIdList,goodsIds);

        SumTotalQuantityRequest sumTotalQuantityRequest = new SumTotalQuantityRequest();

        // 1:权限有限制的  2:入参有涉及仓库参数的需要放入仓库 否则不限制仓库参数 3:传了销售组织
        if (limitPermission || hasWarehouseParams){
            sumTotalQuantityRequest.setWarehouseAreaIdList(warehouseAreaIdList);
        }
        //如果货品id集合不为空则设置货品id列表
        if (CollectionUtils.isNotEmpty(goodsIds)){
            sumTotalQuantityRequest.setGoodsIds(goodsIds);
        }
        sumTotalQuantityRequest.setTypes(Lists.newArrayList(BATCH_INVENTORY,CAR_INVENTORY));
        //获取数据库的合计数量
        log.info("sumInventoryQuantity_sumTotalQuantity_request:{}",JSON.toJSONString(sumTotalQuantityRequest));
        Result<BusinessInventoryDTO> businessInventoryDTOResult = crUnifiedInventoryService.sumTotalQuantity(sumTotalQuantityRequest);
        log.info("sumInventoryQuantity_sumTotalQuantity_result:{}",JSON.toJSONString(businessInventoryDTOResult));
        if (businessInventoryDTOResult == null || businessInventoryDTOResult.getResult() == null){
            return Result.success(null);
        }
        BusinessInventoryDTO businessInventoryDTO = businessInventoryDTOResult.getResult();
        InventorySumQuantityResponse inventorySumQuantityResponse = new InventorySumQuantityResponse();
        inventorySumQuantityResponse.setAvailableQuantity(format(businessInventoryDTO.getAvailableQuantity() - unShippedQuantity));
        inventorySumQuantityResponse.setWithholdingQuantity(format(businessInventoryDTO.getWithholdingQuantity() + unShippedQuantity));
        inventorySumQuantityResponse.setOnWayQuantity(format(businessInventoryDTO.getOnwayQuantity()));
        inventorySumQuantityResponse.setFrozenQuantity(format(businessInventoryDTO.getFrozenQuantity()));
        inventorySumQuantityResponse.setInspectQuantity(format(businessInventoryDTO.getInspectQuantity()));
        inventorySumQuantityResponse.setTotalQuantity(format(businessInventoryDTO.getTotalQuantity()));

        return Result.success(inventorySumQuantityResponse);
    }

    /**
     * 分页查询库存 和库存数量合计 混合请求
     * @param mixQueryInventoryRequest
     * @return
     */
    @Override
    @FacadeInvoker
    public MixQueryInventoryResponse mixQueryInventory(MixQueryInventoryRequest mixQueryInventoryRequest) {
        //校验查询条件 无条件不允许查询
        if (CollectionUtils.isEmpty(mixQueryInventoryRequest.getWarehouseIdList())
                && CollectionUtils.isEmpty(mixQueryInventoryRequest.getWarehouseAreaIdList())
                && StringUtils.isAllBlank(mixQueryInventoryRequest.getGoodsId(),mixQueryInventoryRequest.getGoodsCode(),
                mixQueryInventoryRequest.getFactoryCode(),mixQueryInventoryRequest.getWarehouseCode(),
                mixQueryInventoryRequest.getSaleOrgId())){
            MixQueryInventoryResponse response = new MixQueryInventoryResponse();
            response.setErrorCode("OTS-03-005-00-15-103");
            response.setMessage("请输入查询条件");
            response.setExtData(init(null));
            response.setResult(null);
            response.setSuccess(false);
            return response;
        }
//        if (mixQueryInventoryRequest.getStoreType() != null && StringUtils.isBlank(mixQueryInventoryRequest.getSaleOrgId())){
//            MixQueryInventoryResponse response = new MixQueryInventoryResponse();
//            response.setErrorCode("OTS-03-005-00-15-401");
//            response.setMessage("逻辑仓库类型选中时,销售组织必选");
//            response.setSuccess(false);
//            return response;
//        }
        // 销售组织 + 逻辑仓类型
        //获取当前登录人信息
        EmployeeGetCurrentLoginResponse currentLoginResponse = bcOrderService.employeeGetCurrentLogin();
        if (currentLoginResponse == null || StringUtils.isBlank(currentLoginResponse.getRelatedOrganizationId())
                || StringUtils.isBlank(currentLoginResponse.getRelatedOrganizationType())){
            log.info("sumInventoryQuantity_orgError:{}",JSON.toJSONString(currentLoginResponse));
            MixQueryInventoryResponse response = new MixQueryInventoryResponse();
            response.setErrorCode("OTS-03-005-00-15-105");
            response.setMessage("当前登录人信息获取失败");
            response.setSuccess(false);
            return response;
        }
        String relatedOrganizationId = currentLoginResponse.getRelatedOrganizationId();
        String relatedOrganizationType = currentLoginResponse.getRelatedOrganizationType();

        //构建请求参数
        SumInventoryQuantityRequest sumInventoryQuantityRequest = new SumInventoryQuantityRequest();
        BeanUtils.copyProperties(mixQueryInventoryRequest,sumInventoryQuantityRequest);
        sumInventoryQuantityRequest.setRelatedOrganizationId(relatedOrganizationId);
        sumInventoryQuantityRequest.setRelatedOrganizationType(relatedOrganizationType);


        QueryListWarehouseStockForPageRequest queryListWarehouseStockForPageRequest = new QueryListWarehouseStockForPageRequest();
        BeanUtils.copyProperties(mixQueryInventoryRequest,queryListWarehouseStockForPageRequest);

        //获取数据库的合计数量
        log.info("mixQueryInventory_sumInventoryQuantity_request:{}",JSON.toJSONString(sumInventoryQuantityRequest));
        CompletableFuture<Result<InventorySumQuantityResponse>> sumFuture = CompletableFuture.supplyAsync(() -> {
            return sumInventoryQuantity(sumInventoryQuantityRequest);
        },taskExecutor);

//        //校验仓库数据
//        if (StringUtils.isNotBlank(mixQueryInventoryRequest.getSaleOrgId())){
//            SearchCargoZoneListByDBRequest request = new SearchCargoZoneListByDBRequest();
//            request.setModel(3);
//            request.setSaleOrgId(mixQueryInventoryRequest.getSaleOrgId());
//
//        }
        //获取分页查询结果
        log.info("mixQueryInventory_queryListWarehouseStockForPage_request:{}",JSON.toJSONString(queryListWarehouseStockForPageRequest));
        CompletableFuture<Result<List<BusinessInventoryDTO>>> queryStockFuture = CompletableFuture.supplyAsync(() -> {
            int type = Integer.parseInt(relatedOrganizationType);
            if (type == SALE_ORG_TYPE || type == SALES_CHANNEL_TYPE || type == SALES_DEPARTMENT_TYPE){
                String topCompanyId = getTopCompanyId(relatedOrganizationId);
                if (StringUtils.isBlank(topCompanyId)){
                    log.error("mixQueryInventory_queryListWarehouseStockForPage_error",JSON.toJSONString(sumInventoryQuantityRequest));
                    return Result.success(null);
                }
                //分子公司id
                queryListWarehouseStockForPageRequest.setBizUnitIdList(Lists.newArrayList(topCompanyId));
            }else if (type == COMPANY_TYPE){
                queryListWarehouseStockForPageRequest.setBizUnitIdList(Lists.newArrayList(relatedOrganizationId));
            }else if (type > SALES_DEPARTMENT_TYPE){
                return Result.success(null);
            }
            return crUnifiedInventoryService.queryListWarehouseStockForPage(queryListWarehouseStockForPageRequest);
        },taskExecutor);
        try {
            Result<InventorySumQuantityResponse> inventorySumQuantityResponseResult = sumFuture.get();
            log.info("mixQueryInventory_sumInventoryQuantity_result:{}",JSON.toJSONString(inventorySumQuantityResponseResult));
            Result<List<BusinessInventoryDTO>> listResult = queryStockFuture.get();
            log.info("mixQueryInventory_getListWarehouseStockByPage_result:{}",JSON.toJSONString(listResult));
            MixQueryInventoryResponse response = new MixQueryInventoryResponse();
            //库存合计信息
            if (inventorySumQuantityResponseResult != null && inventorySumQuantityResponseResult.getResult() != null){
                response.setExtData(init(inventorySumQuantityResponseResult.getResult()));
            }
            //分页查询数据
            if (listResult != null){
                response.setResult(listResult.getResult());
                response.setTotal(listResult.getTotal());
            }
            return response;
        }catch (Throwable e){
            log.error("mixQueryInventory_error",e);
            MixQueryInventoryResponse response = new MixQueryInventoryResponse();
            response.setSuccess(false);
            response.setErrorCode("OTS-03-005-00-15-104");
            response.setMessage("库存查询异常");
            return response;
        }
    }

    //生成统计结果
    private InventoryStatistic init(InventorySumQuantityResponse response){
        if (response == null){
            response = new InventorySumQuantityResponse();
            response.setAvailableQuantity("0");
            response.setOnWayQuantity("0");
            response.setWithholdingQuantity("0");
            response.setFrozenQuantity("0");
            response.setInspectQuantity("0");
            response.setTotalQuantity("0");
        }
        InventoryStatistic inventoryStatistic = new InventoryStatistic();
        List<InventoryStatisticData> dataList = Lists.newArrayList();
        InventoryStatisticData availableData = new InventoryStatisticData();
        availableData.setLabel("可用库存汇总:");
        availableData.setValue(response.getAvailableQuantity());
        InventoryStatisticData onWayData = new InventoryStatisticData();
        onWayData.setLabel("在途库存汇总:");
        onWayData.setValue(response.getOnWayQuantity());
        InventoryStatisticData withholdingData = new InventoryStatisticData();
        withholdingData.setLabel("占用库存汇总:");
        withholdingData.setValue(response.getWithholdingQuantity());
        InventoryStatisticData frozenData = new InventoryStatisticData();
        frozenData.setLabel("冻结库存汇总:");
        frozenData.setValue(response.getFrozenQuantity());
        InventoryStatisticData inspectData = new InventoryStatisticData();
        inspectData.setLabel("质检库存汇总:");
        inspectData.setValue(response.getInspectQuantity());
        InventoryStatisticData totalData = new InventoryStatisticData();
        totalData.setLabel("总库存汇总:");
        totalData.setValue(response.getTotalQuantity());
        dataList.add(availableData);
        dataList.add(onWayData);
        dataList.add(withholdingData);
        dataList.add(frozenData);
        dataList.add(inspectData);
        dataList.add(totalData);
        inventoryStatistic.setStatistic(dataList);
        return inventoryStatistic;
    }

    //获取调拨单的未发量
    private Long getUnShippedQuantity(List<String> shareWarehouseAreaIdList,List<String> goodsIds){
        if (CollectionUtils.isEmpty(shareWarehouseAreaIdList)){
            return 0L;
        }
        BatchGetAllocateUnShippedQuantityRequest request = new BatchGetAllocateUnShippedQuantityRequest();
        request.setShipWarehouseAreaIds(shareWarehouseAreaIdList);
        if (CollectionUtils.isNotEmpty(goodsIds)){
            request.setScItemIds(goodsIds);
        }
        Result<List<AllocateUnshippedQuantitySDO>> listResult = crUnifiedInventoryService.batchGetAllocateUnShippedQuantity(request);
        Long unShippedQuantity = 0L;
        if (listResult != null && CollectionUtils.isNotEmpty(listResult.getResult())){
            AllocateUnshippedQuantitySDO allocateUnshippedQuantitySDO = listResult.getResult().get(0);
            Long applyQuantity = allocateUnshippedQuantitySDO.getApplyQuantity() != null ? allocateUnshippedQuantitySDO.getApplyQuantity() : 0L ;
            Long shipQuantity = allocateUnshippedQuantitySDO.getShipQuantity() != null ? allocateUnshippedQuantitySDO.getShipQuantity() : 0L;
            unShippedQuantity = (applyQuantity - shipQuantity ) * 1000;
        }
        return unShippedQuantity;
    }

    //过滤出共享仓类型的仓库id
    private List<String> getShareWarehouseAreaIdList(List<WarehouseInfo> warehouseInfos){
        return warehouseInfos.stream().filter(warehouseInfo -> SHARE_WAREHOUSE_TYPE.equals(warehouseInfo.getType()))
                .map(WarehouseInfo::getId).filter(StringUtils::isNotBlank)
                .collect(Collectors.toList());
    }

    /**
     * 获取逻辑仓库列表信息
     * @param sumInventoryQuantityRequest
     * @param searchCargoZoneListRequest
     * @return
     */
    private List<WarehouseInfo> getWarehouseAreaList(SumInventoryQuantityRequest sumInventoryQuantityRequest ,SearchCargoZoneListByDBRequest searchCargoZoneListRequest){
        if (StringUtils.isNotBlank(sumInventoryQuantityRequest.getFactoryCode())){
            searchCargoZoneListRequest.setExactSapFactoryCode(sumInventoryQuantityRequest.getFactoryCode().trim());
        }
        if (StringUtils.isNotBlank(sumInventoryQuantityRequest.getWarehouseCode())){
            searchCargoZoneListRequest.setExactWarehouseCode(sumInventoryQuantityRequest.getWarehouseCode());
        }
        if (CollectionUtils.isNotEmpty(sumInventoryQuantityRequest.getWarehouseIdList())){
            searchCargoZoneListRequest.setWarehouseIdList(sumInventoryQuantityRequest.getWarehouseIdList());
        }
        if (CollectionUtils.isNotEmpty(sumInventoryQuantityRequest.getWarehouseAreaIdList())){
            searchCargoZoneListRequest.setWarehouseAreaIds(sumInventoryQuantityRequest.getWarehouseAreaIdList());
        }

        //1是仓库档案，3是逻辑仓
        searchCargoZoneListRequest.setModel(3);
        //1启用状态 取消筛选启用状态的
//        searchCargoZoneListRequest.setStatus(1);
        //2共享仓  3销售单元仓 5工厂仓
        searchCargoZoneListRequest.setLimit(MAX_PAGE_SIZE);
        //分页超过1000就报错了
        //这里应该获取的是需要计算共享仓预占的仓库 和实际统计库存的仓库是有区别的.
        log.info("sumInventoryQuantity_searchCargoZoneListByDB_request:{}",JSON.toJSONString(searchCargoZoneListRequest));
        SearchCargoZoneListByDBResponse response = unifiedInventoryService.searchCargoZoneListByDB(searchCargoZoneListRequest);
        log.info("sumInventoryQuantity_searchCargoZoneListByDB_result:{}",JSON.toJSONString(response));
        if (response == null || CollectionUtils.isEmpty(response.getResult())){
            return null;
        }
        // 这个逻辑仓库列表是统计库存需要的列表
        List<WarehouseInfo> warehouseInfos = response.getResult();
        Integer total = response.getTotal();
        if (total > MAX_PAGE_SIZE){
            Integer page = total % MAX_PAGE_SIZE == 0? total / MAX_PAGE_SIZE : total / MAX_PAGE_SIZE + 1;
            List<Future<SearchCargoZoneListByDBResponse>> futureList = Lists.newArrayList();
            for (int i=1 ; i< page ; i++){
                searchCargoZoneListRequest.setStart(i * MAX_PAGE_SIZE);
                SearchCargoZoneListByDBRequest request = new SearchCargoZoneListByDBRequest();
                BeanUtils.copyProperties(searchCargoZoneListRequest,request);
                CompletableFuture<SearchCargoZoneListByDBResponse> future = CompletableFuture.supplyAsync(() -> {
                    SearchCargoZoneListByDBResponse dbResponse = unifiedInventoryService.searchCargoZoneListByDB(request);
                    return dbResponse;
                },taskExecutor);
                futureList.add(future);
            }
            for (Future<SearchCargoZoneListByDBResponse> future : futureList) {
                try{
                    SearchCargoZoneListByDBResponse dbResponse = future.get();
                    if (dbResponse != null && CollectionUtils.isNotEmpty(dbResponse.getResult())){
                        warehouseInfos.addAll(dbResponse.getResult());
                    }
                }catch (Throwable e){
                    log.error("InventoryReadServiceImpl_searchCargoZoneListByDB_error",e);
                }
            }
        }

        if (CollectionUtils.isEmpty(warehouseInfos)){
            return null;
        }
        return warehouseInfos;
    }
    //获取组织下指定到销售组织层级的组织id列表
    private List<String> getDownSaleOrgIds(String orgId){
        GetDownOrganizationListRequest request = new GetDownOrganizationListRequest();
        request.setType(SALE_ORG_TYPE);
        request.setId(orgId);
        Result<List<com.epoch.app.crplatformenhance.sdo.OrganizationSDO>> downOrganizationList = crPlatformEnhanceService.getDownOrganizationList(request);
        if (downOrganizationList == null || CollectionUtils.isEmpty(downOrganizationList.getResult())){
            return null;
        }
        return downOrganizationList.getResult().stream().filter(organizationSDO -> SALE_ORG_TYPE.equals(organizationSDO.getType()))
                .map(com.epoch.app.crplatformenhance.sdo.OrganizationSDO::getId)
                .collect(Collectors.toList());
    }
    private String getTopCompanyId(String orgId){
        GetTopOrganizationListRequest getTopOrganizationListRequest = new GetTopOrganizationListRequest();
        getTopOrganizationListRequest.setType(COMPANY_TYPE);
        getTopOrganizationListRequest.setId(orgId);
        Result<List<TopOrganizationListResponse>> topOrganizationList = crPlatformEnhanceService.getTopOrganizationList(getTopOrganizationListRequest);
        if (topOrganizationList == null || CollectionUtils.isEmpty(topOrganizationList.getResult())){
            return null;
        }
        return topOrganizationList.getResult().stream().filter(topOrganizationListResponse -> COMPANY_TYPE.equals(topOrganizationListResponse.getType()))
                .map(TopOrganizationListResponse::getId)
                .findFirst()
                .orElse(null);
    }
    //获取销售组织id
    private String getSaleOrgId(String orgId){
        GetTopOrganizationListRequest request = new GetTopOrganizationListRequest();
        request.setType(SALE_ORG_TYPE);
        request.setId(orgId);
        Result<List<TopOrganizationListResponse>> topOrganizationList = crPlatformEnhanceService.getTopOrganizationList(request);
        if (topOrganizationList == null || CollectionUtils.isEmpty(topOrganizationList.getResult())){
            return null;
        }
        return topOrganizationList.getResult().stream().filter(topOrganizationListResponse -> SALE_ORG_TYPE.equals(topOrganizationListResponse.getType()))
                .map(TopOrganizationListResponse::getId).findAny().orElse(null);
    }

    /**
     * 获取货品和货品编码的交集(货品id列表)
     * @param request
     * @return
     */
    private List<String> getMixedGoodsIds(SumInventoryQuantityRequest request){
        if (StringUtils.isNotBlank(request.getGoodsCode())){
            BaselineQueryScItemByPageFromDbRequest dbRequest = new BaselineQueryScItemByPageFromDbRequest();
//            dbRequest.setOutIdList(Lists.newArrayList(request.getGoodsCode()));
            //货品编码模糊查询
            dbRequest.setOutId(request.getGoodsCode());
            dbRequest.setBusinessType("11");
            dbRequest.setType(0);//非组合货品
            dbRequest.setLimit(4000);
            dbRequest.setStatusList(Lists.newArrayList(1,-1));
            Object data = baseDataService.baselineQueryScItemByPageFromDb(dbRequest);
            List<ScItemSDO> scItemSDOS = convertResult2ScItemSDOList(data);
            //查不到返回空
            if (CollectionUtils.isEmpty(scItemSDOS)){
                return null;
            }
            //模糊查询返回多个goodsId
            List<String> goodsIdList = scItemSDOS.stream().map(ScItemSDO::getScItemId).collect(Collectors.toList());
            //如果页面选择了goodsId 同时输入了goodsCode 需要判断是否包含了goodsId
            if (StringUtils.isNotBlank(request.getGoodsId())){
                if (goodsIdList.contains(request.getGoodsId())){
                    return Lists.newArrayList(request.getGoodsId());
                }
                return null;
            }else {
                return goodsIdList;
            }

        }
        return null;
    }

    /**
     * 中台货品转换
     * @param data
     * @return
     */
    private List<ScItemSDO> convertResult2ScItemSDOList(Object data){
        if (data == null){
            return null;
        }
        JSONObject object = JSON.parseObject(JSON.toJSONString(data));
        if (object == null){
            return null;
        }
        JSONObject result = object.getJSONObject("result");
        if (result == null){
            return null;
        }
        JSONObject resultJSONObject = result.getJSONObject("result");
        if (resultJSONObject == null){
            return null;
        }
        JSONArray content = resultJSONObject.getJSONArray("content");
        if (content == null || content.size() ==0){
            return null;
        }
        List<ScItemSDO> scItemSDOS = Lists.newArrayList();
        for (int i = 0; i < content.size(); i++) {
            JSONObject jsonObject = content.getJSONObject(i);
            scItemSDOS.add(scItemConverter(jsonObject));
        }
        return scItemSDOS;
    }
    /**
     * 货品模型转换
     * **/
    private ScItemSDO scItemConverter(JSONObject obj) {
        ScItemSDO scItemSDO = new ScItemSDO();
        scItemSDO.setBarCode(obj.getString("barCode"));
        // 这里需要查询品牌
        scItemSDO.setBrandId(obj.getString("brandId"));
        scItemSDO.setScItemId(obj.getString("scItemId"));
        scItemSDO.setLeafCategoryId(obj.getString("leafCategoryId"));
        //  实际蒙牛货品的很多字段都在features中
        scItemSDO.setFeatures((Map) obj.get("features"));
        scItemSDO.setOuterId(obj.getString("outerId"));
        scItemSDO.setTitle(obj.getString("title"));
        scItemSDO.setType(Integer.getInteger(obj.getString("type")));
        scItemSDO.setUnit(obj.getString("unit"));
        scItemSDO.setStatus(Objects.isNull(obj.getString("status")) ? -1 : Double.valueOf(obj.getString("status")).intValue());
        if (Objects.nonNull(obj.getString("gmtModified"))) {
            String gmtModifiedStr = obj.getString("gmtModified");
            Date gmtModified = TimeUtil.parseTime(gmtModifiedStr);
            scItemSDO.setGmtModified(gmtModified);
        }
        if (Objects.nonNull(obj.getString("gmtCreate"))) {
            String gmtCreateStr = obj.getString("gmtCreate");
            Date gmtCreate = TimeUtil.parseTime(gmtCreateStr);
            scItemSDO.setGmtCreate(gmtCreate);
        }
        return scItemSDO;
    }

    //缩小1000倍
    private String format(Long quantity){
        if (quantity == null){
            return "0";
        }
        return new BigDecimal(quantity).movePointLeft(3).stripTrailingZeros().toPlainString();
    }
}
